﻿#include "VideoRecording.h"
#include "ui_VideoRecording.h"
#include <iostream>
#include <windows.h>
#include <QFile>
#include <QDateTime>
#include "RecordingThread.h"
extern "C"
{
#include <libavdevice/avdevice.h>
#include <libavutil/avutil.h>
#include <libavcodec/avcodec.h>
#include <libavformat/avformat.h>
}

#pragma execution_character_set("utf-8")

CVideoRecording::CVideoRecording(QWidget *parent)
    : QWidget(parent)
    , m_ui(new Ui::VideoRecording)
	, m_pFmtCtx(nullptr)
	, m_pFile(nullptr)
	, m_pThread(new CRecordingThread)
{
    m_ui->setupUi(this);
	avdevice_register_all();
	av_register_all();

	AVFormatContext *pFormatCtx = avformat_alloc_context();
	AVDictionary* options = NULL;
	av_dict_set(&options, "list_devices", "true", 0);
	AVInputFormat *iformat = av_find_input_format("dshow");
	puts("Device Option Info======");
	avformat_open_input(&pFormatCtx, "video=dummy", iformat, &options);
	std::cout << "---" << std::endl;
}

CVideoRecording::~CVideoRecording()
{
    delete m_ui;
}

void CVideoRecording::on_btnStartStop_clicked()
{
    if (m_ui->btnStartStop->isChecked())
    {
		startRecording(true);
		m_ui->btnStartStop->setText(QString("结束"));
		m_ui->btnSuspend->setEnabled(true);
    }
    else
    {
		stopRecording(true);
		m_ui->btnStartStop->setText(QString("开始"));
		m_ui->btnSuspend->setEnabled(false);
    }
}

void CVideoRecording::on_btnSuspend_clicked()
{
	if (m_ui->btnSuspend->isChecked())
	{
		m_ui->btnSuspend->setText(QString("继续"));
		stopRecording(false);
	}
	else
	{
		m_ui->btnSuspend->setText(QString("暂停"));
		startRecording(false);
	}
}

char* CVideoRecording::dup_wchar_to_utf8(wchar_t *w)
{
	char *s = NULL;
	int l = WideCharToMultiByte(CP_UTF8, 0, w, -1, 0, 0, 0, 0);
	s = (char *)av_malloc(l);
	if (s)
		WideCharToMultiByte(CP_UTF8, 0, w, -1, s, l, 0, 0);
	return s;
}

void CVideoRecording::startRecording(bool bIsOpenFile)
{
    AVInputFormat* pIFormat = av_find_input_format("dshow");
	wchar_t pw[] = L"video=HP HD Camera";
	char* filename = dup_wchar_to_utf8(pw);
	AVDictionary* options = nullptr;
	av_dict_set(&options, "video_size", "640x480", 0);
	av_dict_set(&options, "framerate", "30", 0);
	av_dict_set(&options, "pixel_format", "yuyv422", 0);
    int res = avformat_open_input(&m_pFmtCtx, filename, pIFormat, &options);
    if (res < 0)
    {
        std::cout << "打开设备失败!" << std::endl;
        return;
    }
    else
    {
        std::cout << "打开设备成功!" << std::endl;
    }
	if (bIsOpenFile)
	{
		QString strFilePath = QString("C:/Users/ymm/Desktop/video_%1.h264")
			.arg(QDateTime::currentDateTime().toString("yyyyMMddhhmmss"));
		m_pFile = new QFile(strFilePath);
		if (!m_pFile->open(QIODevice::ReadWrite | QIODevice::Append))
		{
			m_ui->btnStartStop->setEnabled(false);
			return;
		}
	}
	
	if (m_pThread != nullptr)
	{
		m_pThread->setFormatContext(m_pFmtCtx);
		m_pThread->setRecordStatus(true);
		m_pThread->setFile(m_pFile);
		m_pThread->start();
	}
}

void CVideoRecording::stopRecording(bool bIsCloseFile)
{
	m_pThread->setFormatContext(nullptr);
	m_pThread->setRecordStatus(false);
	m_pThread->quit();
	m_pThread->wait();
	m_pThread->setFile(nullptr);
	if (m_pFmtCtx != nullptr)
	{
		avformat_close_input(&m_pFmtCtx);
		m_pFmtCtx = nullptr;
	}
	if (bIsCloseFile && m_pFile)
	{
		m_pFile->close();
	}
}

